package com.stenio.fancat.service.login;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.concurrent.TimeUnit;

import com.stenio.fancat.domain.user.UserIconImage;
import com.stenio.fancat.domain.user.UserRelationship;
import com.stenio.fancat.domain.user.UserRelationshipCandy;
import com.stenio.fancat.domain.user.UserRelationshipLog;
import com.stenio.fancat.mapper.user.UserIconImageMapper;
import com.stenio.fancat.mapper.user.UserRelationshipCandyMapper;
import com.stenio.fancat.mapper.user.UserRelationshipLogMapper;
import com.stenio.fancat.mapper.user.UserRelationshipMapper;
import com.stenio.fancat.util.TokenProccessor;
import com.stenio.fancat.util.TokenUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.stenio.fancat.exception.FanCatException;
import com.stenio.fancat.form.LoginForm;
import com.stenio.fancat.util.JsonUtil;
import com.stenio.fancat.util.StringUtil;
import com.stenio.fancat.vo.LoginVO;

/**
 * 登录模块服务实现类
 *
 */
@Service
public class LoginService {

	@Autowired
	private StringRedisTemplate redis;

	@Autowired
	private UserRelationshipMapper userRelationshipMapper;

	@Autowired
	private UserRelationshipCandyMapper userRelationshipCandyMapper;

	@Autowired
	private UserRelationshipLogMapper userRelationshipLogMapper;


	/**
	 * 登录方法
	 * @param form
	 * @return
	 * @throws FanCatException
	 */
	@Transactional
	public LoginVO login(LoginForm form){
		if (null == form) {
			throw new RuntimeException("参数错误,不能为空");
		}

		UserRelationship userRelationship = getUser(form.getUnionId());  //数据库查询是否存在此用户

		if(userRelationship == null){
			userRelationship = new UserRelationship();   //新用户，添加至数据库中
			userRelationship.setUserId(StringUtil.getUUID());
			userRelationship.setUnionId(form.getUnionId());
			userRelationship.setPhone(form.getPhone());
			userRelationship.setName(form.getName());
			userRelationship.setOpenId(form.getOpenId());
			userRelationship.setIcon(form.getIcon());
			Date date = new Date();
			userRelationship.setCreateTime(date);
			userRelationship.setUpdateTime(date);
			userRelationship.setState(0);
			userRelationshipMapper.insert(userRelationship);//新用户，添加至数据库中
			UserRelationshipCandy userRelationshipCandy = new UserRelationshipCandy();   //新用户，添加至数据库中,这是糖果币账户
			userRelationshipCandy.setUserId(userRelationship.getUserId());
			userRelationshipCandy.setIncreaseCandy(0);
			userRelationshipCandy.setReduceCandy(0);
			userRelationshipCandy.setCreateTime(date);
			userRelationshipCandy.setUpdateTime(date);
			userRelationshipCandyMapper.insert(userRelationshipCandy);

			UserRelationshipLog userRelationshipLog = new UserRelationshipLog();//新用户，添加至数据库中log表
			userRelationshipLog.setUpdateTime(date);
			userRelationshipLog.setCreateTime(date);
			userRelationshipLog.setAfterCandy(0);
			userRelationshipLog.setBeforeCandy(0);
			userRelationshipLog.setCandy(0);
			userRelationshipLog.setOperType(1);
			userRelationshipLog.setUserId(userRelationship.getUserId());
			userRelationshipLogMapper.insert(userRelationshipLog);

		}
//		String newToken = TokenProccessor.getInstance().makeToken();   //生成Token
//		String json = JsonUtil.toJson(userRelationship);   // 将对象转换为json串
//		redis.opsForValue().set(newToken,json,7*24,TimeUnit.DAYS);   // 存放到Redis中

		LoginVO v = new LoginVO();
		v.setUserId(userRelationship.getUserId());

		//v.setToken(newToken);
		return v;
	}

	/**
	 * 监听用户打开小程序后判断是否需要置换Token
	 * @param token
	 * @param userRelationship
	 * @return
	 * @throws com.stenio.fancat.common.FanCatException
	 */
	public String isReplaceToken(String token, UserRelationship userRelationship)throws com.stenio.fancat.common.FanCatException {
		if(! validate(token)){
			throw new RuntimeException("未知的token或 token已过期");// 终止置换 跳转到登录页面
		}
		Date TokenGenTime;// token生成时间
		try {
			String[] tokenDetails = token.split("_");
			SimpleDateFormat formatter = new SimpleDateFormat("yyyyMMddHHmmss");
			TokenGenTime = formatter.parse(tokenDetails[1]);
		} catch (ParseException e) {
			e.printStackTrace();
			throw new com.stenio.fancat.common.FanCatException("token格式错误:" + token);
		}

		// token已产生时间
		long passed = Calendar.getInstance().getTimeInMillis()
				- TokenGenTime.getTime();

		if(passed < 6*24*60*60*1000){  // 置换保护期内
			return token;
		}

		// 置换token
		String newToken = TokenProccessor.getInstance().makeToken();
		StringRedisTemplate redis = new StringRedisTemplate();
		String json = JsonUtil.toJson(userRelationship);   // 将对象转换为json串
		redis.opsForValue().set(newToken,json,7*24, TimeUnit.DAYS);   // 存放到Redis中
		delete(token);  //删除原有的Token
		return newToken;
	}


	/**
	 * 通过unionId查询用户
	 * @param unionId
	 * @return
	 */
	public UserRelationship getUser(String unionId) {
		return userRelationshipMapper.selectUserInfoByUId(unionId);
	}


	/**
	 * 校验redis中的token和传递的token
	 * @param token
	 * @return
	 */
	public boolean validate(String token){
		String tokenDB = redis.opsForValue().get(token);
		if (tokenDB != null && tokenDB.equals(token)) {
			return true;
		}
		return false;
	}

	/**
	 * 根据key键删除缓存（用户对象）
	 * @param token
	 */
	public void delete(String token){
		redis.delete(token);
	}

}
